/**
 * 六边形基础指标
 */

using UnityEngine;
namespace GameGraphics.HomeWorld
{
    public static class HexMetrics
    {
        /// <summary>
        /// 六边形外圈半径
        /// </summary>
        public static float OuterRadius = 0.5f;
        /// <summary>
        /// 六边形内圈半径
        /// </summary>
        public static float InnerRadius = OuterRadius * 0.866025404f;
        /// <summary>
        /// 相对固定区域
        /// </summary>
        public const float SolidFactor = 0.98f;
        /// <summary>
        /// 桥接区域占比
        /// </summary>
        public const float BlendFactor = 1f - SolidFactor;

        /// <summary>
        /// 六个顶点
        /// </summary>
        public static Vector3[] Corners =
        {
            new Vector3(0f, 0f, OuterRadius),
            new Vector3(InnerRadius, 0f, 0.5f * OuterRadius),
            new Vector3(InnerRadius, 0f, -0.5f * OuterRadius),
            new Vector3(0f, 0f, -OuterRadius),
            new Vector3(-InnerRadius, 0f, -0.5f * OuterRadius),
            new Vector3(-InnerRadius, 0f, 0.5f * OuterRadius),
            new Vector3(0f, 0f, OuterRadius),
        };

        /// <summary>
        /// 获取指定位置的Corner
        /// </summary>
        /// <param name="index"></param>
        /// <returns></returns>
        public static Vector3 GetCorner(int index)
        {
            return Corners[index] * SolidFactor;
        }

        /// <summary>
        /// 获取桥接
        /// </summary>
        public static Vector3 GetBridge(int i, int j)
        {
            return (Corners[i] + Corners[j]) * BlendFactor;
        }

        /// <summary>
        /// 根据索引坐标获取中心位置
        /// </summary>
        public static Vector3 GetCenterPosition(int x, int z)
        {
            Vector3 position;
            position.x = (x + z * 0.5f - z / 2) * (InnerRadius * 2f);
            position.y = 0f;
            position.z = z * (OuterRadius * 1.5f);
            return position;
        }

        /// <summary>
        /// (野外版本)根据索引坐标获取中心位置
        /// </summary>
        /// <param name="x"></param>
        /// <param name="z"></param>
        /// <returns></returns>
        public static Vector3 GetCenterPosition1(int x, int z)
        {
            var OuterRadius = 1.504f;
            var InnerRadius = OuterRadius * 0.866025404f;
            Vector3 position;
            position.x = (x + z * 0.5f - z / 2) * (InnerRadius * 2f);
            position.y = 0f;
            position.z = z * (OuterRadius * 1.5f);
            return position;
        }

        /// <summary>
        /// 普通坐标转六边形坐标系
        /// </summary>
        public static Vector2Int FromPosition(Vector3 position)
        {
            float x = position.x / (InnerRadius * 2f);
            float y = -x;
            float offset = position.z / (OuterRadius * 3f);
            x -= offset;
            y -= offset;

            int iX = Mathf.RoundToInt(x);
            int iY = Mathf.RoundToInt(y);
            int iZ = Mathf.RoundToInt(-x - y);

            if (iX + iY + iZ != 0)
            {
                float dX = Mathf.Abs(x - iX);
                float dY = Mathf.Abs(y - iY);
                float dZ = Mathf.Abs(-x - y - iZ);

                if (dX > dY && dX > dZ)
                {
                    iX = -iY - iZ;
                }
                else if (dZ > dY)
                {
                    iZ = -iX - iY;
                }
            }
            return new Vector2Int(iX + iZ / 2, iZ);
        }
        public static Vector2Int FromPosition1(Vector3 position)
        {
            var OuterRadius = 1.504f;
            var InnerRadius = OuterRadius * 0.866025404f;
            float x = position.x / (InnerRadius * 2f);
            float y = -x;
            float offset = position.z / (OuterRadius * 3f);
            x -= offset;
            y -= offset;

            int iX = Mathf.RoundToInt(x);
            int iY = Mathf.RoundToInt(y);
            int iZ = Mathf.RoundToInt(-x - y);

            if (iX + iY + iZ != 0)
            {
                float dX = Mathf.Abs(x - iX);
                float dY = Mathf.Abs(y - iY);
                float dZ = Mathf.Abs(-x - y - iZ);

                if (dX > dY && dX > dZ)
                {
                    iX = -iY - iZ;
                }
                else if (dZ > dY)
                {
                    iZ = -iX - iY;
                }
            }
            return new Vector2Int(iX + iZ / 2, iZ);
        }

        /// <summary>
        /// rqs转普通坐标
        /// </summary>
        public static Vector2Int ToNomalCoordinates(int x, int z)
        {
            //x - z / 2, z
            return new Vector2Int(x + z / 2, z);
        }
    }
}
